package com.uoko.common.collection;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Comparator;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
import java.util.function.Consumer;

/**
 * <p>
 *
 * </p>
 *
 * @author chenyingchun
 * Email qiaohai@uoko.com
 * created by 2018/6/6 0006
 */
public class SortList<T> extends ArrayList<T> {

	/**
	 * 
	 */
	private Comparator<? super T> comparator;

	private boolean isSort = false;

	public SortList() {
		this.comparator = Comparators.OBJECT_COMPARATOR;
	}

	/**
	 * 
	 * @param comparator
	 */
	public SortList(Comparator<? super T> comparator) {
		this.comparator = comparator;
	}

	@Override
	public boolean add(T element) {
		this.isSort = false;
		return super.add(element);
	}

	@Override
	public void add(int index, T element) {
		this.isSort = false;
		super.add(index, element);
	}

	@Override
	public boolean addAll(Collection<? extends T> c) {
		this.isSort = false;
		return super.addAll(c);
	}

	@Override
	public boolean addAll(int index, Collection<? extends T> c) {
		this.isSort = false;
		return super.addAll(index, c);
	}

	@Override
	public void sort(Comparator<? super T> c) {
		// TODO Auto-generated method stub
		this.comparator = c;
		this.isSort = false;
		this.sort();
	}

	@Override
	public void forEach(Consumer<? super T> action) {
		// TODO Auto-generated method stub
		this.sort();
		super.forEach(action);
	}

	@Override
	public int indexOf(Object o) {
		// TODO Auto-generated method stub
		this.sort();
		return super.indexOf(o);
	}

	@Override
	public int lastIndexOf(Object o) {
		// TODO Auto-generated method stub
		this.sort();
		return super.lastIndexOf(o);
	}

	@Override
	public Object[] toArray() {
		// TODO Auto-generated method stub
		this.sort();
		return super.toArray();
	}

	@SuppressWarnings("hiding")
	@Override
	public <T> T[] toArray(T[] a) {
		// TODO Auto-generated method stub
		this.sort();
		return super.toArray(a);
	}

	@Override
	public T get(int index) {
		// TODO Auto-generated method stub
		this.sort();
		return super.get(index);
	}

	@Override
	public T set(int index, T element) {
		// TODO Auto-generated method stub
		this.sort();
		return super.set(index, element);
	}

	@Override
	public T remove(int index) {
		// TODO Auto-generated method stub
		this.sort();
		return super.remove(index);
	}

	@Override
	public ListIterator<T> listIterator(int index) {
		// TODO Auto-generated method stub
		this.sort();
		return super.listIterator(index);
	}

	@Override
	public ListIterator<T> listIterator() {
		// TODO Auto-generated method stub
		this.sort();
		return super.listIterator();
	}

	@Override
	public Iterator<T> iterator() {
		// TODO Auto-generated method stub
		this.sort();
		return super.iterator();
	}

	@Override
	public List<T> subList(int fromIndex, int toIndex) {
		// TODO Auto-generated method stub
		this.sort();
		return super.subList(fromIndex, toIndex);
	}

	@Override
	protected void removeRange(int fromIndex, int toIndex) {
		// TODO Auto-generated method stub
		this.sort();
		super.removeRange(fromIndex, toIndex);
	}

	/**
	 * 
	 * @return
	 */
	public boolean isSorted() {
		return isSort;
	}

	/**
	 * 
	 */
	public void sort() {
		if (isSort || this.comparator == null)
			return;
		syncSort();
	}

	/**
	 * 进行排序,綫程同步
	 */
	private synchronized void syncSort() {
		if (!isSort) {
			super.sort(this.comparator);
			isSort = true;
		}
	}

	@SuppressWarnings({ "unchecked", "rawtypes" })
	@Override
	public Object clone() {
		// TODO Auto-generated method stub
		SortList<T> list = new SortList<>(this.comparator);
		list.addAll((ArrayList) super.clone());
		return list;
	}

}
